import { Awake1System } from "../../../../../Core/Module/EventSystem/IAwakeSystem";
import { DestroySystem } from "../../../../../Core/Module/EventSystem/IDestroySystem";
import { Log } from "../../../../../Core/Module/Log/Log";
import { ATimer } from "../../../../../Core/Module/Timer/ATimer";
import { TimerComponent } from "../../../../../Core/Module/Timer/TimerComponent";
import { ExpandOf, FriendOf, InvokeAttribute, ObjectSystemAttribute } from "../../../../../Decorator/Decorator";
import { AIComponent } from "../../../../Model/Share/Module/AI/AIComponent";
import { TimerInvokeType } from "../../../../Model/Share/TimerInvokeType";

/**
 * 使用 Expand 扩展方法
 * 
 * 必须作出以下申明，才能调用对象的扩展方法
 */
declare module "../../../../Model/Share/Module/AI/AIComponent" {

    interface AIComponent {

        Check(): void;
        Cancel(): void;

    }

}

@ExpandOf(AIComponent)
export class AIComponentSystem {

    private static Check(self: AIComponent): void {
        if (self.Parent == null) {
            TimerComponent.Instance.Remove(self.Timer);
            return;
        }
    }

    private static Cancel(self: AIComponent): void {
        self.CancellationToken?.Cancel();
        self.Current = 0;
        self.CancellationToken = null;
    }

}

@InvokeAttribute(TimerInvokeType.AITimer)
export class AITimer extends ATimer<AIComponent> {

    protected override Run(self: AIComponent) {
        try {
            self.Check();
        } catch (e) {
            Log.Error(`move timer error: ${self.Id}\n${e}`);
        }
    }
}

@FriendOf(AIComponent)
@ObjectSystemAttribute()
export class AIComponentAwake1System extends Awake1System<AIComponent, number> {

    Awake(self: AIComponent, aiConfigId: number): void {
        self.AIConfigId = aiConfigId;
        self.Timer = TimerComponent.Instance.NewRepeatedTimer(1000, TimerInvokeType.AITimer, self);
    }

}

@FriendOf(AIComponent)
@ObjectSystemAttribute()
export class AIComponentDestroySystem extends DestroySystem<AIComponent> {

    Destroy(self: AIComponent): void {
        TimerComponent.Instance?.Remove(self.Timer);
        self.CancellationToken?.Cancel();
        self.CancellationToken = null;
        self.Current = 0;
    }

}